<template>
    <div style="width: 100%;height: 100%">
        <div v-if="busSolution.navigationPosition=='horizontal'" class="FormBusSolutionShow">
            <div class="FormBusSolutionShow_button">
                <a-button
                    v-if="canSave && current < formSolutions.length -1 && !readOnly && mode=='form'"
                    type="primary"

                    @click="save"
                >
                    {{ $ti18('rxForm.saveBtn', '保存') }}
                </a-button>
                <a-button v-if="canSave && current == formSolutions.length - 1 && !readOnly" type="primary"  @click="submit">
                    {{ $ti18('rxForm.commitBtn', '提交') }}
                </a-button>
                <a-button  @click="prev">
                    {{ i18n('previous', '上一步') }}
                </a-button>
                <a-button  type="primary" @click="next">
                    {{ i18n('nextStep', '下一步') }}
                </a-button>
            </div>
            <div class="FormBusSolutionShow_asteps" :style="`width:${formAllConfig.allWidth}`">
                <a-steps :current="current" size="small" :direction="busSolution.navigationPosition">
                    <a-step v-for="item in formSolutions" :status="item.status" :key="item.idx_"
                            :title="item.navigationName"/>
                </a-steps>
            </div>
            <div style="flex: 1;overflow: auto;position: relative;" :key="`key_${current}`">
                <div class="bus-solution-roll" :style="`max-width:${formAllConfig.allWidth};margin:auto;width:100%;`" >
                    <div class="previewBox" v-if="mode === 'form' && curForm.formConfig">
                        <x-form-build
                            :key="`key_${current}`"
                            ref="formBuild"
                            :form-data="curForm.formData"
                            :form-config="curForm.formConfig"
                            :global-config="curForm.globalConfig"
                            :contextData="curForm.contextData"
                            :permission="curForm.permission"
                            :form-js="curForm.formJs"
                            :readOnly="readOnly"
                            :alias="curForm.formAlias"
                            :name="curFormSolution.name"
                            :dialogBox="dialogBox"
                            :id-field="curForm.idField"
                        ></x-form-build>
                    </div>
                    <form-bo-list-preview
                        v-else-if="mode=='list'"
                        ref="boList"
                        :params="curListParams"
                        :alias="curListKey"
                        :customVm="getCurVm"
                    ></form-bo-list-preview>
                    <component v-else ref="customView" :is="customView" :busFormData="busFormData" :readOnly="readOnly"  style="width: 100%;height: 100%"></component>
                </div>
            </div>
        </div>
    </div>
</template>

<script>
import FormSolutionApi from "@/common/api/form/formSolution.js";
import FormBusinessSolutionApi from "@/common/api/form/formBusinessSolution.js";
import {Util} from "@lowcode/jpaas-base-lib";
import DialogBox from "@/assets/js/dialogBox";
import AppUtil from "../../../../assets/js/AppUtil";
import {defineAsyncComponent } from 'vue'
export default {
    name: "FormBusSolutionShow",
    components: {
        FormBoListPreview:defineAsyncComponent(()=>import('@/views/modules/form/FormBoListPreview/FormBoListPreview.vue'))
    },
    props: {
        alias: {
            type: String
        },
        busSolId: {
            type: [String, Number]
        },
        rowData: {
            type: Object
        },
        /**
         * 不使用主键打开表单数据。
         * {
         *     param1:"",
         *     param2:""
         * }
         */
        params: {
            type: Object
        },
        readOnly: {
            type: Boolean,
            default: false
        },
        setInitData: {
            type: Function
        },
    },
    data() {
        return {
            dialogBox: DialogBox,
            //业务方案配置得表单方案
            formSolutions: [],
            //表单业务数据
            formBusInstData: [],
            //业务方案
            busSolution: {},
            //当前表单方案
            curFormSolution: {},
            //当前导航
            current: 0,
            //业务表单数据 用于存放表单得数据
            busFormData: {},
            //业务表单是否能保存
            busCanSave: {},
            //主表单方案
            mainSolution: {
                alias: "",
                relPk: ""
            },
            formAllConfig: {
                allWidth: "1300px",
                bg: "#fff"
            },
            mode: "form",
            customView: "",
            curListKey: "",
            curListParams: "",
            //拖拽表单
            curForm: {
                formJs: "",
                formConfig: "",
                globalConfig: "",
                formData: {},
                formAlias: "",
                idField: "",
                permission: {},
                contextData: {}
            },
        }
    },
    computed: {
        canSave() {
            return this.busCanSave[this.curFormSolution.value];
        }
    },
    created() {
        this.getBusinessSolution();
    },
    methods: {
        i18n(name, text, key) {
            return this.$ti18(name, text, "formBusinessSolution", key);
        },
        //获取业务方案
        getBusinessSolution() {
            if (this.alias) {
                let mainPk = this.rowData ? this.rowData["ID_"] : "";
                FormBusinessSolutionApi.getByAliasAndMainPk(this.alias, mainPk).then(res => {
                    if (res.success) {
                        this.busSolution = res.data.busSolution;
                        this.formBusInstData = res.data.formBusInstData;
                        this.mainSolution = JSON.parse(this.busSolution.mainFormSolution);
                    }
                });
            }
        },
        init(data, alias, pkId, params, callback) {
            let self_ = this;
            this.curForm.formAlias = alias;
            FormSolutionApi.getByAlias(alias, pkId, params).then(res => {
                self_.$nextTick(() => {
                    self_.busFormData[alias] = res.data;
                    self_.busCanSave[alias] = res.canSave;
                    if (res.metadata) {
                        let formConfig = JSON.parse(res.metadata);
                        if (formConfig) {
                            res.formConfig = formConfig;
                        }
                        if (this.setInitData) {
                            let _data = res.data;
                            res.data = Object.assign(res.data, this.setInitData(_data));
                        }
                        if (callback) {
                            callback();
                        }
                        this.initForm(res);
                    }
                })
            })
        },
        initForm(res) {
            if (!res.contextData) {
                res.contextData = {};
            }
            if (res.data.INST_ID_) {
                let contextDetail = {
                    instId: res.data.INST_ID_
                };
                Object.assign(res.contextData, contextDetail);
            } else if (!this.pkId && this.formSolution && this.formSolution.flowDefMapping) {
                //新增时获取绑定的流程设计主键
                let flows = JSON.parse(this.formSolution.flowDefMapping);
                let defId = "";
                if (flows && flows.length > 0) {
                    defId = flows[0].defId;
                }
                let contextDetail = {
                    defId: defId
                };
                Object.assign(res.contextData, contextDetail);
            }
            this.curForm.formJs = res.script;
            this.curForm.formConfig = res.formConfig;
            this.curForm.globalConfig = res.globalConfig ? JSON.parse(res.globalConfig) : {};
            this.curForm.permission = res.permission;
            this.curForm.contextData = res.contextData;
            this.curForm.formData = res.data;
            this.curForm.formAlias = res.alias;
            this.curForm.idField = res.idField;
            this.$forceUpdate()
        },
        //初始化业务表单的表单数据
        initBusFormData(alias, pkId) {
            let self = this;
            FormSolutionApi.getByAlias(alias, pkId).then(res => {
                self.busFormData[alias] = res.data;
                self.busCanSave[alias] = res.canSave;
                //是否为当前表单
                if (self.curFormSolution.value == alias) {
                    let formConfig = JSON.parse(res.metadata);
                    if (formConfig) {
                        res.formConfig = formConfig;
                    }
                    self.initForm(res);
                }
            })
        },
        /**
         * 下一步
         * @returns {Promise<void>}
         */
        async next() {
            let self = this;
            if (this.mode == "form") {
                let formData = this.$refs.formBuild.getData();
                this.busFormData[this.curFormSolution.value] = formData;
            }
            if (this.current < this.formSolutions.length - 1) {
                //处理当前页面函数
                let curSol = self.formSolutions[self.current];
                //只读与自定义页面不需要验证必填
                if (!this.readOnly && curSol.mode != "custom") {
                    let validResult = await this.validForm(true);
                    if (!validResult.success) {
                        this.$message.warning(validResult.msg);
                        return;
                    }
                }
                //处理下一步的条件函数
                let nextSol = self.formSolutions[self.current + 1];
                let result = this.handleNextFunc(nextSol, self.current + 1, "next");
                if (result.success) {
                    this.$message.warning(result.message);
                    return;
                }
                self.mode = nextSol.mode;
                //下一个
                this.formSolutions[this.current].status = "finish";
                this.current = result.index || this.current + 1;
                this.formSolutions[this.current].status = "process";
                //显示自定义页面
                if ("custom" == nextSol.mode) {
                    self.customView = AppUtil.loadComponent(nextSol.formSolution);
                    return;
                } else if ("list" == nextSol.mode) {
                    //列表参数
                    if (nextSol.relField) {
                        self.curListParams = self.getParams(JSON.parse(nextSol.relField));
                    }
                    //列表
                    self.curListKey = nextSol.list ? JSON.parse(nextSol.list).value : "";
                    return;
                }
                this.curFormSolution = JSON.parse(this.formSolutions[this.current].formSolution);
                this.curFormSolution["relField"] = this.formSolutions[this.current].relField;
                let relPk = "";
                if (self.formBusInstData && self.formBusInstData.length > 0) {
                    relPk = self.getRelPk(this.curFormSolution.value);
                }else {
                    relPk = this.rowData ? this.rowData["ID_"] : "";
                }
                let pk = "";
                let params = {};
                if (this.curFormSolution.relField != "ID_") {
                    params[this.curFormSolution.relField] = relPk;
                } else {
                    pk = relPk;
                }
                this.init(this.busFormData[this.curFormSolution.value], this.curFormSolution.value, pk, params, this.handleCurFunc);
            } else {
                this.$message.warning(self.i18n('noNextStep', '无下一步!'));
            }
        },
        //上一步
        prev() {
            if (this.current != 0) {
                //当前为表单
                if ("form" == this.mode) {
                    let formData = this.$refs.formBuild.getData();
                    this.busFormData[this.curFormSolution.value] = formData;
                }
                let result = {};
                if (this.current - 1 >= 0) {
                    //处理下一步的条件函数
                    result = this.handleNextFunc(this.formSolutions[this.current - 1], this.current - 1, "prev");
                    if (result.success) {
                        this.$message.warning(result.message);
                        return;
                    }
                }
                this.formSolutions[this.current].status = "wait";
                this.current = result.index || this.current - 1;
                this.formSolutions[this.current].status = "process";
                let prevSol = this.formSolutions[this.current];
                this.mode = prevSol.mode;
                //上一步页面为自定义页面
                if (prevSol.mode == "custom") {
                    this.customView = AppUtil.loadComponent(prevSol.formSolution);
                    return;
                } else if ("list" == prevSol.mode) {
                    //列表
                    this.curListKey = prevSol.list ? JSON.parse(prevSol.list).value : "";
                    return;
                }
                this.curFormSolution = JSON.parse(this.formSolutions[this.current].formSolution);
                this.curFormSolution["relField"] = this.formSolutions[this.current].relField;
                let relPk = "";
                if (this.formBusInstData && this.formBusInstData.length > 0) {
                    relPk = this.getRelPk(this.curFormSolution.value);
                }else {
                    relPk = this.rowData ? this.rowData["ID_"] : "";
                }
                let pk = "";
                let params = {};
                if (this.curFormSolution.relField != "ID_") {
                    params[this.curFormSolution.relField] = relPk;
                } else {
                    pk = relPk;
                }
                this.init(this.busFormData[this.curFormSolution.value], this.curFormSolution.value, pk, params);
            } else {
                this.$message.warning(this.$ti18('noUpStep', '无上一步!', 'formBusinessSolution'));
            }
        },
        //表单验证
        async validForm(required) {
            if (!this.$refs.formBuild || !this.$refs.formBuild.formVm || this.mode != "form") {
                return {success: true, msg: this.$ti18('msg.verifyPass', '验证通过', 'formBusinessSolution')};
            }
            let formVm = this.$refs.formBuild.formVm;
            //提交前校验
            if (formVm._beforeSubmit) {
                let rtn = await formVm._beforeSubmit("submit");
                if (!rtn.success) {
                    return rtn;
                }
            }
            //数据必填，类型校验
            let res = formVm.valid(required, true);
            if (!res.success) {
                return res;
            }
            //表单唯一性校验
            let validMainUnique = await formVm.validMainUnique();
            if (!validMainUnique.success) {
                return validMainUnique;
            }
            return {success: true, msg: this.$ti18('msg.verifyPass', '验证通过', 'formBusinessSolution')};
        },
        //获取表单关联值
        getRelPk(formSolAlias) {
            let obj = this.formBusInstData.find(item => item.relFormsolAlias == formSolAlias);
            return obj ? obj.relPk : "";
        },
        //获取表单方案配置
        getFormSolution(alias) {
            let formSolutions = JSON.parse(this.busSolution.formSolutions);
            let formSolution = formSolutions.find(item => {
                if (JSON.parse(item.formSolution).value == alias) {
                    return item;
                }
            });
            return formSolution;
        },

        //处理当前页面的下一步函数
        handleCurFunc() {
            let curSol = this.formSolutions[this.current - 1];
            if (!curSol.formSolution) {
                return;
            }
            let formSolution = JSON.parse(curSol.formSolution);
            if (curSol.extendFunc) {
                let curSolExtendFunc = JSON.parse(curSol.extendFunc);
                if (curSolExtendFunc.nextFunc) {
                    let func = new Function("formData", "busFormData", curSolExtendFunc.nextFunc);
                    let formData = {};
                    //当前为表单
                    if (this.mode == "form") {
                        formData = this.busFormData[formSolution.value];
                    }
                    func.bind(this)(formData, this.busFormData);
                }
            }
        },
        //处理下一步页面的跳过条件函数
        handleNextFunc(formSolution, index, type) {
            let success = true;
            let message = "";
            let self = this;
            //下一页面为最后的表单则不判断条件
            if (index + 1 == this.formSolutions.length) {
                return {success: false, message: ""};
            }
            //下一步
            if (type == "next") {
                //处理下一步页面的条件
                if (formSolution.extendFunc) {
                    let formSolutionExtendFunc = JSON.parse(formSolution.extendFunc);
                    if (formSolutionExtendFunc.condition) {
                        let func = new Function("busFormData", formSolutionExtendFunc.condition);
                        success = func.bind(this)(this.busFormData);
                    }
                }
                if (success) {
                    if (index + 1 < this.formSolutions.length) {
                        return this.handleNextFunc(self.formSolutions[index + 1], index + 1, type);
                    }
                    return {success: success, message: self.i18n('noNextTips', '无下一步或后续都不符合条件!')};
                }
            }
            //上一步
            else if (type == "prev") {
                //处理上一步页面的条件
                if (formSolution.extendFunc) {
                    let formSolutionExtendFunc = JSON.parse(formSolution.extendFunc);
                    if (formSolutionExtendFunc.condition) {
                        let func = new Function("busFormData", formSolutionExtendFunc.condition);
                        success = func.bind(this)(this.busFormData);
                    }
                }
                if (success) {
                    if (index > 0) {
                        return this.handleNextFunc(self.formSolutions[index - 1], index - 1, type);
                    } else {
                        return {success: false, message: ""};
                    }
                }
            }
            return {success: success, message: message, index: index};
        },
        getCurVm() {
            return this;
        },
        /**
         * 参数 例如 name=ray&address=guangzhou
         * @param relFields
         * @returns {string}
         */
        getParams(relFields) {
            let params = [];
            for (let i = 0; i < relFields.length; i++) {
                let relField = relFields[i];
                if (relField.relField && relField.listField && relField.relSolution) {
                    let value = this.busFormData[relField.relSolution][relField.relField];
                    if (!value) {
                        continue;
                    }
                    if (relField.isSingle === 0 && value) {
                        value = JSON.parse(value).value;
                    }
                    let obj = {
                        "key": relField.listField,
                        "value": value
                    }
                    params.push(obj);
                }
            }
            let paramStr = "";
            for (let i = 0; i < params.length; i++) {
                if (i != 0) {
                    paramStr += "&";
                }
                paramStr += params[i].key + "=" + params[i].value;
            }
            return paramStr;
        },
        /**
         * 保存当前表单
         * 注:主表单得数据会先保存
         * @returns {Promise<void>}
         */
        async save() {
            //表单验证
            let validResult = await this.validForm(true);
            if (!validResult.success) {
                this.$message.warning(validResult.msg);
                return;
            }
            let self = this;
            this.$confirm({
                title: self.$ti18('rxMsa.actionTips', '操作提示'),
                content: self.i18n('saveCurFormTips', '确定要保存当前表单数据吗?'),
                okText: self.$ti18('rxForm.ackBtn', '确认'),
                cancelText: self.$ti18('rxForm.cancelBtn', '取消'),
                zIndex: 99999,
                onOk() {
                    let data = [];
                    let formData = self.$refs.formBuild.getData();
                    self.removeSpaces(formData);
                    let currentSolution = self.curFormSolution.value;
                    let mainSolution = self.mainSolution.value;
                    //先将当前表单数据存放到busFormData
                    if (!self.busFormData[currentSolution]) {
                        self.busFormData[currentSolution] = formData;
                    }
                    //判断当前是否为主表单
                    if (currentSolution != self.mainSolution.value && !self.busFormData[mainSolution].ID_) {
                        data.push({
                            setting: {action: "save", alias: mainSolution},
                            data: self.busFormData[mainSolution],
                            relField: self.mainSolution.relField
                        });
                    }
                    data.push({
                        setting: {action: "save", alias: currentSolution},
                        data: formData, relField: self.curFormSolution.relField
                    });
                    let relField = self.mainSolution.relField ? self.mainSolution.relField : "ID_";
                    let mainPk = self.busFormData[self.mainSolution.value][relField];
                    let parameter = {
                        action: "save",
                        busSolutionId: self.busSolution.id,
                        mainPk: mainPk ? mainPk : "",
                        data: data
                    }
                    FormBusinessSolutionApi.saveBusForm(parameter).then(res => {
                        if (!res.success) {
                            return;
                        }
                        for (let i = 0; i < res.data.length; i++) {
                            //提交后事件处理
                            if (self.$refs.formBuild.formVm._afterSubmit) {
                                self.$refs.formBuild.formVm._afterSubmit(res.data[i], res.data[i].data);
                            }
                            let pk = res.data[i].data.pk;
                            let solutionAlias = res.data[i].data.solutionAlias;
                            self.initBusFormData(solutionAlias, pk)
                        }
                    })
                },
                onCancel() {
                }
            });
        },
        async submit() {
            if (this.mode == "form") {
                let validResult = await this.validForm(true);
                if (!validResult.success) {
                    this.$message.warning(validResult.msg);
                    return;
                }
            }
            let self = this;
            this.$confirm({
                title: self.$ti18('rxMsa.actionTips', '操作提示'),
                content: self.i18n('saveAllFormTips', '确定要保存所有表单数据吗?'),
                okText: self.$ti18('rxForm.ackBtn', '确认'),
                cancelText: self.$ti18('rxForm.cancelBtn', '取消'),
                zIndex: 99999,
                onOk() {
                    let data = [];
                    if (self.mode == "form") {
                        //先将当前表单数据存放到busFormData
                        let formData = self.$refs.formBuild.getData();
                        self.busFormData[self.curFormSolution.value] = formData;
                    }
                    let arr = Object.keys(self.busFormData);
                    for (let i = 0; i < arr.length; i++) {
                        self.removeSpaces(self.busFormData[arr[i]]);
                        let formSolution = self.getFormSolution(arr[i]);
                        data.push({
                            setting: {action: "save", alias: arr[i]},
                            data: self.busFormData[arr[i]],
                            relField: formSolution ? formSolution.relField : ""
                        });
                    }
                    let relField = self.mainSolution.relField ? self.mainSolution.relField : "ID_";
                    let mainPk = self.busFormData[self.mainSolution.value][relField];
                    let parameter = {
                        action: "submit",
                        busSolutionId: self.busSolution.id,
                        mainPk: mainPk ? mainPk : "",
                        data: data
                    }
                    FormBusinessSolutionApi.saveBusForm(parameter).then(res => {
                        if (!res.success) {
                            return;
                        }
                        Util.closeWindow(self, 'ok', res.data);
                    })
                },
                onCancel() {
                }
            });
        },
        /**
         * 删除对象空格。
         * @param _data
         */
        removeSpaces(_data) {
            //清除字段前后空格；
            for (let key in _data) {
                let item = _data[key];
                if (typeof item == "string" && item != "") {
                    _data[key] = item.trim();
                } else if (item && Object.prototype.toString.call(item) == "[object Array]") {
                    let _self = this;
                    item.forEach((item, idx) => {
                        _self.removeSpaces(item);
                    })
                } else if (item && Object.prototype.toString.call(item) == "[object Object]") {
                    this.removeSpaces(item);
                }
            }
        },
    },
    watch: {
        "busSolution": function (val) {
            if (val && val.formSolutions) {
                this.formSolutions = JSON.parse(val.formSolutions);
                this.formSolutions.find(item => {
                    item.status = "wait";
                });
                if (this.formSolutions[0].formSolution) {
                    this.curFormSolution = JSON.parse(this.formSolutions[0].formSolution);
                    this.curFormSolution["relField"] = this.formSolutions[0].relField;
                    this.mainSolution["relField"] = this.formSolutions[0].relField;
                    let pk = "";
                    let params = {};
                    if (this.formBusInstData) {
                        let formBusData = this.formBusInstData.find(item => item.relFormsolAlias == this.mainSolution.value);
                        if (formBusData && formBusData["relPk"] && this.mainSolution["relField"] != "ID_") {
                            params[this.mainSolution["relField"]] = formBusData["relPk"];
                        } else {
                            pk = this.rowData ? this.rowData["ID_"] : "";
                        }
                    }
                    this.formSolutions[0].status = "process";
                    this.init(null, this.curFormSolution.value, pk, params);
                }
            }
        }
    },
}
</script>

<style scoped>
.FormBusSolutionShow {
    display: flex;
    flex-direction: column;
    overflow: hidden;
    height: 100%;
    padding:0 10px;
}

.FormBusSolutionShow_button {
    background-color: #ffffff;
    border: solid 1px #e8e8e8;
    padding:6px 10px;
    text-align: right;
    margin-left: -10px;
    margin-right: -10px;
}

.FormBusSolutionShow_button > button{
    margin-left: 6px;
}

.FormBusSolutionShow_asteps {
    max-width: 1300px;
    background-color: #ffffff;
    box-shadow: 0px 0px 4px 0px rgba(44, 62, 83, 0.21);
    border-radius: 5px;
    padding: 12px 16px ;

    margin: 19px auto;
}

.FormBusSolutionShow .previewBox::v-deep(.x-build-form-box){
    padding: 0;
}
.FormBusSolutionShow .previewBox::v-deep(.x-form-build-box){
    margin: 0;
    overflow: initial;
    height: 100%;
}
.bus-solution-roll{
    position: absolute;
    inset: 0;
}
</style>
